package com.mybatisplus.mp.service.impl;

import com.mybatisplus.mp.mapper.TbUserMapper;
import com.mybatisplus.mp.mapper.UserMapper;
import com.mybatisplus.mp.pojo.TbUser;
import com.mybatisplus.mp.pojo.User;
import com.mybatisplus.mp.service.UserCacheService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheConfig;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service;

/**
 * 如果我们在此注解中定义cacheNames，则此类中的所有方法上 @Cacheable的cacheNames默认都是此值。当然@Cacheable也可以重定义cacheNames的值
 */
@Service
@CacheConfig(cacheNames = "user1")
public class UserCacheServiceImpl implements UserCacheService {
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private TbUserMapper tbUserMapper;

    /**
     * cacheNames 设置缓存的值
     * key：指定缓存的key，这是指参数id值。
     * key可以使用spEl表达式
     * key也可以指定对象的成员变量#user.id
     * 如果不定义，则使用全部的参数计算一个key值
     */
    @Cacheable(cacheNames = "users", key = "#id")
    @Override
    public User queryByid(int id) {
        System.out.println("进入业务层");
        User user = userMapper.selectById(id);
        TbUser tbUser = tbUserMapper.selectById(id);
//        return userMapper.selectById(id);
        return user;
    }

    /**
     * keyGenerator 定义key生成的类，和key的不能同时存在
     *
     * @param id
     * @return
     */
    @Cacheable(cacheNames = "user2", keyGenerator = "myKeyGenerator")
    @Override
    public User queryByid2(int id) {
        System.out.println("进入业务层");
        return userMapper.selectById(id);
    }

    /**
     * 条件缓存：
     * 只有满足condition的请求才可以进行缓存，如果不满足条件，则跟方法没有@Cacheable注解的方法一样
     * 如下面只有id>0进行缓存
     */
    @Override
    @Cacheable(cacheNames = "user3", condition = "T(java.lang.Integer).valueOf(#id)>0")
    public User queryByid3(int id) {
        System.out.println("进入业务层");
        return userMapper.selectById(id);
    }

    /**
     * 条件缓存：
     * 对不满足unless的记录，才进行缓存
     * "unless expressions" are evaluated after the method has been called
     * 如下面：只对不满足返回 'T(java.lang.Integer).parseInt(#result.id) <3 ' 的记录进行缓存
     */
    @Override
    @Cacheable(cacheNames = "user4", unless = "T(java.lang.Integer).valueOf(#id)<0")
    public User queryByid4(int id) {
        System.out.println("进入业务层");
        return userMapper.selectById(id);
    }

    /**
     * allEntries = true: 清空缓存book1里的所有值
     */
    @Override
    @CacheEvict(cacheNames = "user1", allEntries = true) //删除缓存
    public void clear() {

    }

    /**
     * allEntries = false: 默认值，此时只删除key对应的值
     *
     * @param id
     */
    @Override
    @CacheEvict(cacheNames = "user1", key = "#id")
    public void clear(int id) {

    }

    /**
     * 每次执行都会执行方法，无论缓存里是否有值，同时使用新的返回值的替换缓存中的值。
     *
     * @param id
     */
    @CachePut(cacheNames = "user1", key = "#id")
    @Override
    public User update(int id) {
        System.out.println("进入业务层");
        return userMapper.selectById(id);
    }


}
